package org.kenewstar.file.service.impl;

import org.checkerframework.checker.units.qual.A;
import org.kenewstar.common.bean.dto.FileAndFolderDto;
import org.kenewstar.common.bean.pojo.MicroActualFile;
import org.kenewstar.common.bean.pojo.MicroFile;
import org.kenewstar.common.bean.pojo.MicroUser;
import org.kenewstar.common.constant.CommonConstant;
import org.kenewstar.common.utils.CommonUtil;
import org.kenewstar.file.config.PathProperties;
import org.kenewstar.file.dto.AddFolderDto;
import org.kenewstar.file.dto.DiskFileData;
import org.kenewstar.file.dto.UpdateNameDto;
import org.kenewstar.file.mapper.ActualFileMapper;
import org.kenewstar.file.mapper.FileMapper;
import org.kenewstar.file.mapper.FolderMapper;
import org.kenewstar.file.service.FileService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.UUID;

/**
 * @author xinke.huang@hand-china.com
 * @version 1.0
 * @date 2021/2/28
 */
@Service
public class FileServiceImpl implements FileService {
    @Resource
    private FileMapper fileMapper;
    @Resource
    private FolderMapper folderMapper;
    @Resource
    private ActualFileMapper actualFileMapper;
    @Resource
    private PathProperties pathProperties;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public List<FileAndFolderDto> uploadFile(Long fid,MultipartFile file, MicroUser user) throws IOException {
        // 获取文件名
        String filename = file.getOriginalFilename();
        // 文件后缀名
        String suffix = "";
        assert filename != null;
        if (filename.contains(".")){
            suffix = filename.substring(filename.lastIndexOf('.'));
        }
        String diskFilename = UUID.randomUUID() + suffix;
        // 文件路径
        String path = pathProperties.getStorePath()+ diskFilename;
        // 构造文件对象
        File localFile = new File(path);
        // 构造MicroFile对象
        MicroFile microFile = new MicroFile();
        microFile.setFilename(filename);
        microFile.setFileByte(file.getSize());
        microFile.setFolderId(fid);
        microFile.setUserId(user.getId());
        microFile.setFileType(suffix.length() != 0 ? suffix.substring(1) : suffix);
        // 实际文件对象
        MicroActualFile actualFile = new MicroActualFile(diskFilename);
        // 插入实际文件表
        actualFileMapper.insertActualFile(actualFile);

        microFile.setActualId(actualFile.getId());
        fileMapper.insertFile(microFile);

        // 查询当前文件夹内容
        AddFolderDto dto = new AddFolderDto();
        dto.setUid(user.getId());
        dto.setPid(fid);
        List<FileAndFolderDto> dtoList = folderMapper.selectFileAndFolderById(dto);
        // 将文件保存至本地
        file.transferTo(localFile);
        return dtoList;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateName(UpdateNameDto dto) {
        if (Objects.equals(dto.getType(), CommonConstant.FILE)){
            // 修改文件
            return fileMapper.updateFileName(dto);
        }
        // 修改文件夹名称
        return folderMapper.updateFolderName(dto);
    }

    @Override
    public MicroFile getFileById(Long id) {
        return fileMapper.selectFileById(id);
    }

    @Override
    public List<FileAndFolderDto> searchFiles(Integer id, String filename) {
        return fileMapper.selectFilesByLike(id,filename);
    }

    @Override
    public List<DiskFileData> totalUsedFileSize(MicroUser user) {
        Long byteSum = fileMapper.selectSumFileByte(user.getId());
        long sum = Objects.isNull(byteSum) ? 0 : byteSum;
        List<DiskFileData> dataList = new ArrayList<>(2);
        DiskFileData dataUsed = new DiskFileData();
        dataUsed.setName("已使用");
        dataUsed.setY(sum);
        dataUsed.setSize(CommonUtil.byte2Size(sum));
        dataList.add(dataUsed);
        DiskFileData dataNotUsed = new DiskFileData();
        dataNotUsed.setName("未使用");
        dataNotUsed.setY(user.getDiskSize() * CommonConstant.GB - sum);
        dataNotUsed.setSize(CommonUtil.byte2Size(user.getDiskSize() * CommonConstant.GB - sum));
        dataList.add(dataNotUsed);
        return dataList;
    }

    @Override
    public List<MicroFile> selectFilesByPid(Integer uid, Long pid) {
        return fileMapper.selectFilesByPid(uid, pid);
    }
}
